泛型是程式設計的一種特性,允許開發者在強類型語言時定義一些可變部分。
泛型通常用來表達一種未定的資料型態,例如在寫函數時,如果這個函數有參數,開發者需要明確參數的類型。我們要實現一個函數,其功能將對兩個inout且類型相同的參數進行值的交換。
// 定義泛型 T
func exchange<T>(param1:inout T,parma2:inout T){
let tmp = param1
param1 = parma2
parma2 = tmp
}
var p1 = "4"
var p2 = "5"
exchange(param1: &p1, parma2: &p2)
print(p1,p2)// 印出 5,4
泛型除了可以用來定義函數的參數類型以外,在定義資料型態時,也可以起到十分重要的作用,在宣告集合類型時,開發者設置這些集合類型中所要存儲的元素,也可以透過泛型來實現。
// 定義一個struct,ItemType為struct中的泛型
struct Stack<ItemType> {
// 內部有關元素的操作都使用ItemType
var items:[ItemType] = []
mutating func push(param:ItemType){
self.items.append(param)
}
mutating func pop()->ItemType{
return self.items.removeLast()
}
}
// 整型struct
var stack = Stack<Int>()
stack.push(param: 1)
stack.push(param: 2)
stack.pop()
print(stack.items)//1 先進後出
在Swift中還有擴展的用法,其作用是為已經存在的資料型態添加新的功能,後面會說擴展。
// 定義一個struct,ItemType為struct中的泛型
struct Stack<ItemType> {
// 內部有關元素的操作都使用ItemType
var items:[ItemType] = []
mutating func push(param:ItemType){
self.items.append(param)
}
mutating func pop()->ItemType{
return self.items.removeLast()
}
}
// 為Stack添加一個擴展
extension Stack {
func getArrary() -> [ItemType]{
return items
}
}
var stack2 = Stack<Int>()
使用繼承的方式約束泛型的類型,約束該泛型必須透過某一基類或是繼承來實現。
// 定義一個基類
class MyClass1 {
}
struct Stack2<ItemType : MyClass1> {
var items:[ItemType] = []
mutating func push(param:ItemType){
self.items.append(param)
}
mutating func pop()->ItemType{
return self.items.removeLast()
}
}
協定也是Swift中一個重要結構,後面也會說協定,提前使用協定來進行泛型約束的演示。
// 使用協定来约束泛型
protocol MyProtocol {
}
struct Stack3<ItemType : MyProtocol> {
var items:[ItemType] = []
mutating func push(param:ItemType){
self.items.append(param)
}
mutating func pop()->ItemType{
return self.items.removeLast()
}
}
其實在協定中,泛型還有其他的應用,可以使用associatedtype關鍵字來進行關聯,當實現此協議時,具體類型才會被指定。
/// 定義一個協定
protocol MyProtocol2 {
associatedtype ItemType
var param:ItemType {get set}
func printParam(param:ItemType)->Void;
}
// 定義一個class
class MyCalssP:MyProtocol2 {
// 進行計算屬性的實現
var param: Int {
get {
return 0
}
set {
}
}
func printParam(param: Int) {
print(param)
}
}
接下來,是擴展的介紹